package zjy.android.guideapplication

import android.content.Context
import android.graphics.Canvas
import android.graphics.Paint
import android.graphics.Path
import android.graphics.Region
import android.os.Build
import android.util.AttributeSet
import android.widget.FrameLayout
import java.util.*

class GuideView : FrameLayout {
    private val groups: MutableList<GuideGroup> = ArrayList()
    private val path: Path = Path()
    private val paint: Paint = Paint()
    private val nextCallback: Callback = object : Callback {
        override fun callback() {
            next()
        }
    }
    private val finishCallback: Callback = object : Callback {
        override fun callback() {
            finish()
        }
    }
    var onFinishListener: OnFinishListener? = null

    constructor(context: Context) : super(context) {
        init()
    }

    constructor(context: Context, attrs: AttributeSet?) : super(context, attrs) {
        init()
    }

    constructor(context: Context, attrs: AttributeSet?, defStyleAttr: Int) : super(context, attrs, defStyleAttr) {
        init()
    }

    private fun init() {
        setWillNotDraw(false)
    }

    fun setGroups(groups: List<GuideGroup>?) {
        this.groups.clear()
        this.groups.addAll(groups!!)
        update()
    }

    private operator fun next() {
        if (groups.size == 1) {
            finish()
        } else {
            groups.removeAt(0)
            update()
        }
    }

    private fun finish() {
        onFinishListener?.onFinish()
    }

    private fun update() {
        removeAllViews()
        for (guide in groups[0].getGuides()) {
            val view = guide.onCreateGuideLayout(context, nextCallback, finishCallback)
            if (view != null) {
                addView(view)
                setOnClickListener(null)
            } else {
                setOnClickListener { next() }
            }
        }
    }

    override fun onDraw(canvas: Canvas) {
        super.onDraw(canvas)
        if (groups.size == 0) return
        val group = groups[0]
        path.reset()
        paint.reset()
        for (guide in group.getGuides()) {
            guide.onDrawHighlight(canvas, path, paint)
        }
        if (Build.VERSION.SDK_INT < Build.VERSION_CODES.O) {
            canvas.clipPath(path, Region.Op.DIFFERENCE)
        } else {
            canvas.clipOutPath(path)
        }
        canvas.drawColor(resources.getColor(R.color.alpha))
    }

    interface OnFinishListener {
        fun onFinish()
    }
}